package com.example.bbang.service;

import com.example.bbang.entity.User;
import com.example.bbang.mapper.UserMapper;
import org.redisson.api.RLock;
import org.redisson.api.RedissonClient;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.relational.core.sql.In;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.List;
import java.util.concurrent.TimeUnit;

@Service
public class UserService {
    @Resource
    UserMapper userMapper;

    @Autowired
    private RedissonClient redissonClient;


    @Autowired
    private RedisTemplate<String, Object> redisTemplate;

    public List <User> findAll(){
        return userMapper.findAll();
    }


    public User save(User user) {
        userMapper.save(user);
        return user;
    }
    public List <User> findElseAll(String  username){
        return userMapper.findElseAll(username);
    }
    public User updateById(User user) {
        userMapper.updateById(user);
        return user;
    }

    public void deleteById(Integer userID) {
        userMapper.deleteById(userID);

    }

    public User login(String username, String password,Integer status) {
        return userMapper.login(username,password,status);

    }


    public List <User> findBsUser() {
        return userMapper.findBsUser();
    }

    public List <User> ms(String username) {
        return userMapper.ms(username);
    }

    public User updateByPassword(User user) {
        userMapper.updateByPassword(user);
        return user;
    }

    public Integer getUserCountByStatus(Integer status) {
       return userMapper.getUserCountByStatus(status);
    }


//    public List<User> getUserByUsername(String username) {
//        // 从Redis中获取用户信息
//        List<User> user = (List<User>) redisTemplate.opsForValue().get(username);
//        if (user == null) {
//            // 如果Redis中没有，则从数据库中获取并缓存到Redis中
//            // 这里省略了从数据库获取用户的代码
//            // 从数据库获取用户信息
//            user = userMapper.ms(username);
//            System.out.println("redis中没有");
//            redisTemplate.opsForValue().set(username, user);
//            System.out.println("存数据"+redisTemplate.opsForValue().get(username));
//
//        }
//        else{
////            System.out.println("redis中有");
////            redisTemplate.opsForValue().get(username);
//            System.out.println("redis中有"+redisTemplate.opsForValue().get(username));
//            redisTemplate.delete(username);
//            System.out.println("删除后："+redisTemplate.opsForValue().get(username));
//        }
//
//        return user;
//    }


    public List<User> getUserByUsername(String username) {
        RLock lock = redissonClient.getLock("lock:" + username);
        try {
            // 尝试获取锁，最多等待10秒，锁的超时时间为30秒
            boolean isLocked = lock.tryLock(10, 30, TimeUnit.SECONDS);
            if (!isLocked) {
                throw new RuntimeException("Failed to acquire lock for " + username);
            }

            // 从Redis中获取用户信息
            List<User> user = (List<User>) redisTemplate.opsForValue().get(username);
            if (user == null) {
                // 如果Redis中没有，则从数据库中获取并缓存到Redis中
                user = userMapper.ms(username);
                System.out.println("redis中没有");
                redisTemplate.opsForValue().set(username, user);
                System.out.println("存数据" + redisTemplate.opsForValue().get(username));
            } else {
                System.out.println("redis中有" + redisTemplate.opsForValue().get(username));
                redisTemplate.delete(username);
                System.out.println("删除后：" + redisTemplate.opsForValue().get(username));
            }

            return user;
        } catch (InterruptedException e) {
            Thread.currentThread().interrupt();
            throw new RuntimeException("Interrupted while waiting for lock", e);
        } finally {
            // 释放锁
            if (lock.isHeldByCurrentThread()) {
                lock.unlock();
            }
        }
    }

}
